/*
 * PANERadioElement.cpp
 *
 *  Created on: May 2, 2009
 *      Author: wrice
 */
#include "PANEImp.h"
namespace PANEImp {

string PANERadioElement::TagName = "RADIO";

struct PANERadioElement::Imp {

	static bool isSelected( PANERadioElement * radio, EventTarget * target ) {
		if( false == radio->isAnyElementSelected() ) return false;
		Node * const node = dynamic_cast< Node * >( target );
		return NodeImp::getMyIndexOnParent( node ) == radio->getSelectedElement();
		return false;
	}

	class MouseOverEventListener : IMPLEMENTS( EventListener ) {
	public:
		MouseOverEventListener( PANERadioElement * radio )
		: radio_(radio)
		{}

		virtual void handleEvent(Event * evt) {
			EventTarget * const target = evt->getTarget();
			if( radio_ != dynamic_cast< Node * >( target )->getParentNode() ) return;

			if( isSelected( radio_, target ) )
				evt->stopPropagation();
		}

	private:
		PANERadioElement * radio_;
	};

	class MouseDownEventListener : IMPLEMENTS( EventListener ) {
	public:
		MouseDownEventListener( PANERadioElement * radio )
		: radio_(radio)
		{}

		virtual void handleEvent(Event * evt) {
			EventTarget * const target = evt->getTarget();
			if( radio_ != dynamic_cast< Node * >( target )->getParentNode() ) return;

			if( isSelected( radio_, target ) ) return;
			VisualButtonForPANE * const previouslySelectedBtn = dynamic_cast< VisualButtonForPANE * >( radio_->getChildNodes()->item( radio_->getSelectedElement() ) );
			previouslySelectedBtn->setButtonState( VisualButtonForPANE::ButtonNormalState );

			radio_->setSelectedElement( NodeImp::getMyIndexOnParent(dynamic_cast< Node *>( target )) );
		}

	private:
		PANERadioElement * radio_;
	};

	class MouseOutEventListener : IMPLEMENTS( EventListener ) {
	public:
		MouseOutEventListener( PANERadioElement * radio )
		: radio_(radio)
		{}

		virtual void handleEvent(Event * evt) {
			EventTarget * const target = evt->getTarget();
			if( radio_ != dynamic_cast< Node * >( target )->getParentNode() ) return;

			if( isSelected( radio_, target ) ) evt->stopPropagation();
		}

	private:
		PANERadioElement * radio_;
	};

};

PANERadioElement::PANERadioElement(PANEDocument * doc )
: PANEElement( TagName, doc )
, indexOfSelectedElement_(0)
, isAnySelected_(false)
{
	this->addEventListener( MouseEventImp::EVENT_MOUSE_OVER, new Imp::MouseOverEventListener(this), true );
	this->addEventListener( MouseEventImp::EVENT_MOUSE_DOWN, new Imp::MouseDownEventListener(this), true );
	this->addEventListener( MouseEventImp::EVENT_MOUSE_UP, new Imp::MouseOverEventListener(this), true );
	this->addEventListener( MouseEventImp::EVENT_MOUSE_OUT, new Imp::MouseOutEventListener(this), true );
}

unsigned long PANERadioElement::getSelectedElement() {
	return indexOfSelectedElement_;
}

void PANERadioElement::setSelectedElement( unsigned long indexOfButton ) {
	if( indexOfButton >= getChildNodes()->getLength() ) return;
	isAnySelected_ = true;
	indexOfSelectedElement_ = indexOfButton;
}


void PANERadioElement::render( IplImage * img ) {
	if( false == isRepaintRequested() ) return;
	if( false == getVisible() ) return;

	repainted();
}

bool PANERadioElement::isAnyElementSelected() {
	return isAnySelected_;
}

void PANERadioElement::setDeselected() {
	isAnySelected_ = false;
}

}
